package t232

import "sync"

// MyQueue type
type MyQueue struct {
	Items []int
	lock  sync.RWMutex
}

// Constructor : Initialize your data structure here. */
func Constructor() MyQueue {
	return MyQueue{}
}

// RPush : element x to the back of queue. */
func (m *MyQueue) Push(x int) {
	m.lock.Lock()
	m.Items = append(m.Items, x)
	m.lock.Unlock()
}

// LPop : Removes the element from in front of queue and returns that element. */
func (m *MyQueue) Pop() int {
	m.lock.Lock()
	pop := m.Items[0]
	m.Items = m.Items[1:]
	m.lock.Unlock()
	return pop
}

// Peek : Get the front element. */
func (m *MyQueue) Peek() int {
	m.lock.Lock()
	peek := m.Items[0]
	m.lock.Unlock()
	return peek
}

// Empty : Returns whether the queue is empty. */
func (m *MyQueue) Empty() bool {
	m.lock.Lock()
	res := true
	if len(m.Items) > 0 {
		res = false
	}
	m.lock.Unlock()
	return res
}

/**
 * Your MyQueue object will be instantiated and called as such:
 * obj := Constructor();
 * obj.RPush(x);
 * param_2 := obj.LPop();
 * param_3 := obj.Peek();
 * param_4 := obj.Empty();
 */
